<template>
  <q-dialog ref="dialogRef" @hide="onDialogHide">
    <q-card style="min-width: 430px; max-width: 550px">
      <q-toolbar>
        <q-toolbar-title>{{ title }}</q-toolbar-title> <q-btn icon="close" round flat @click="onDialogCancel" />
      </q-toolbar>
      <q-separator />
      <q-card-section>
        <q-list>
          <q-item v-if="cfg.showRemark">
            <q-item-section side>导入说明</q-item-section>
            <q-item-section class="overflow-auto text-green" style="max-height: 130px; white-space: pre-wrap">
              <!-- eslint-disable-next-line vue/no-v-html -->
              <div v-html="cfg.importRemark"></div>
            </q-item-section>
          </q-item>

          <q-item v-if="cfg.showBasicData">
            <q-item-section side> 基础数据 </q-item-section>
            <q-item-section class="cursor-pointer text-blue-14 q-pl-sm" @click="handleBasic"> {{ cfg.basicDataFileName }}</q-item-section>
          </q-item>

          <q-item>
            <q-item-section side> 导入模板 </q-item-section>
            <q-item-section class="cursor-pointer text-blue-14 q-pl-sm" @click="handleTemplate"> {{ cfg.templateName }}</q-item-section>
          </q-item>

          <q-item class="q-pb-none">
            <q-item-section side> 选择文件 </q-item-section>
            <q-item-section>
              <!-- prettier-ignore -->
              <q-file ref="fileRef" v-model="file" filled :max-file-size="maxFileSize" accept=".xls,.xlsx" :rules="[required]" hide-bottom-space label-slot @rejected="onRejected">
                <template #label>点击选择文件（最大{{ maxFileLabel }}）</template>
                <template #prepend> <q-icon name="excel" /> </template>
              </q-file>
            </q-item-section>
          </q-item>
        </q-list>
      </q-card-section>

      <q-card-actions align="right" class="q-pr-xl">
        <q-btn v-close-popup>取消</q-btn>
        <q-btn color="primary" :icon="mdiUpload" :loading="loading" @click="handleUpload">导入</q-btn>
      </q-card-actions>
    </q-card>
  </q-dialog>
</template>

<script setup lang="ts">
  import { onMounted, ref, nextTick } from 'vue';
  import { mdiUpload } from '@quasar/extras/mdi-v6';
  import { useDialogPluginComponent, format, QRejectedEntry, QFile } from 'quasar';

  import { Message } from 'src/utils';
  import { required } from 'src/utils/validator';
  import { request, downloadBlobFile } from 'src/utils';

  interface Props {
    importKey: string; //导入配置键值，必须
    title?: string; // 窗口标题
    maxFileSize?: number; // 单个文件的最大大小（以字节为单位）
    params?: {
      // 其它业务相关的参数参数
      [key: string]: string | number | undefined;
    };
  }
  const props = withDefaults(defineProps<Props>(), {
    title: '数据导入',
    maxFileSize: 5 * 1024 * 1024,
    params: undefined,
  });
  defineEmits(['after-upload', ...useDialogPluginComponent.emits]);

  const { dialogRef, onDialogHide, onDialogOK, onDialogCancel } = useDialogPluginComponent();

  // 上传文件的接口地址
  const baseUrl = '/api/excel/upload';

  // 选择的文件
  const file = ref(null);
  const { humanStorageSize } = format;
  const maxFileLabel = humanStorageSize(props.maxFileSize);

  // 根据上传类别查询配置参数
  const cfg = ref({ templateName: '', showBasicData: false, basicDataFileName: '', showRemark: false, importRemark: '' });
  onMounted(() => {
    // eslint-disable-next-line @typescript-eslint/no-explicit-any
    request.get(baseUrl + '/config', { params: getParams() }).then((data: any) => {
      cfg.value.templateName = data.templateName;
      cfg.value.showBasicData = data.showBasicData;
      cfg.value.basicDataFileName = data.basicDataFileName;
      cfg.value.showRemark = data.showRemark;
      cfg.value.importRemark = data.importRemark;
    });
  });

  // 下载基础数据
  function handleBasic() {
    request.get(baseUrl + '/basicdata', { params: getParams(), responseType: 'blob' }).then((res) => {
      downloadBlobFile(res);
    });
  }

  // 下载导入模板
  function handleTemplate() {
    request.get(baseUrl + '/template', { params: getParams(), responseType: 'blob' }).then((res) => {
      downloadBlobFile(res);
    });
  }

  // 上传文件
  const loading = ref(false);
  const fileRef = ref<QFile>();
  function handleUpload() {
    const success = fileRef.value?.validate() as boolean;
    if (success) {
      const formData = new FormData();
      formData.append('file', file.value!);
      formData.append('importKey', props.importKey);
      request
        .post(baseUrl, formData, { params: getParams(), headers: { 'Content-Type': 'multipart/form-data' } })
        .then((data) => {
          Message.success('上传成功');
          onDialogOK(data);
        })
        .finally(() => {
          file.value = null;
          nextTick(() => fileRef.value?.resetValidation());
        });
    }
  }

  // 不符合规则时给出提示
  function onRejected(files: QRejectedEntry[]) {
    const file = files[0];
    if (file.failedPropValidation == 'accept') {
      Message.warning('只能选择Excel文件');
      return;
    }
    if (file.failedPropValidation == 'max-file-size') {
      Message.warning('文件大小不能超过' + maxFileLabel);
      return;
    }
  }

  function getParams() {
    return Object.assign({}, props.params, { importKey: props.importKey });
  }
</script>

<style scoped>
  :deep(.q-card__actions) {
    padding-right: 30px;
  }
</style>
